//------------------------------------------------------------------------------
// <copyright file="RpcResponse.cpp" company="Microsoft">
//     Copyright (c) Microsoft Corporation.  All rights reserved.
// </copyright>
//------------------------------------------------------------------------------

#include "stdafx.h"

#include "RpcResponse.h"
#include "RpcArchiveImpl.h"

#ifndef _DURANGO
	#include <ObjBase.h>
#endif

using namespace Microsoft::Internal::GamesTest::Rpc::Server;

const wchar_t ArchiveKey[] = L"archive";
const wchar_t HookErrorCodeKey[] = L"hookErrorCode";
const wchar_t RpcErrorCodeKey[] = L"rpcErrorCode";
const wchar_t RequestIdKey[] = L"requestId";

GAMESTEST_ANNOTATE_HRESULT_METHOD HRESULT RpcResponse::Serialize(std::wstring& result)
{
	JsonNode jsonObject;

	jsonObject.SetValue(ArchiveKey, m_archive.GetJson());
	jsonObject.SetValue(HookErrorCodeKey, m_hookErrorCode);
	jsonObject.SetValue(RpcErrorCodeKey, m_rpcErrorCode);
	jsonObject.SetValue(RequestIdKey, (int)m_requestId);

	result = jsonObject.Serialize();

	return S_OK;
}

GAMESTEST_ANNOTATE_HRESULT_METHOD HRESULT RpcResponse::Parse(const wchar_t* data, RpcResponse* response)
{
	HRESULT hr = E_FAIL;

	VERIFY_PARAM_NOT_NULL(response);

	try
	{
		JsonNode jsonResponse;
		jsonResponse.Parse(data);

		response->m_hookErrorCode = (RpcHookCode)jsonResponse.GetIntegerValue(HookErrorCodeKey);
		response->m_rpcErrorCode = (HRESULT)jsonResponse.GetIntegerValue(RpcErrorCodeKey);
		response->m_requestId = jsonResponse.GetIntegerValue(RequestIdKey);
		response->m_archive = RpcArchiveImpl(jsonResponse.GetValue(ArchiveKey));
	}
	catch (std::out_of_range)
	{
		// Key not found error
		hr = E_INVALID_PROTOCOL_FORMAT;
		goto end;
	}
	catch (std::invalid_argument)
	{
		// Parse error
		if (data == nullptr || wcslen(data) == 0)
		{
			hr = E_INVALIDARG;
		}
		else
		{
			hr = E_INVALID_PROTOCOL_FORMAT;
		}

		goto end;
	}

end:
	return hr;
}